package time

import (
	"fmt"
	"strings"
	time2 "time"
)

type Time time2.Time

const (
	timeFormat = "2006-01-02 15:04:05"
)

//Usage:
//type Person struct {
//	ID int `json:"id"`
//	Name     string `json:"name"`
//	Birthday Time `json:"birthday"`
//}

//func main() {
//	src := `{"id":5,"name":"xiaoming","birthday":"2016-06-30 16:09:51"}`
//	p := new(Person)
//	err := json.Unmarshal([]byte(src), p)
//	//var p Person
//	//err := json.Unmarshal([]byte(src), &p)
//	if err != nil {
//		log.Fatal(err)
//	}
//	log.Printf("%+v",p)
//}


func (t *Time) UnmarshalJSON(data []byte) (err error)  {
	now, err := time2.ParseInLocation(`"` + timeFormat + `"`,string(data),time2.Local)

	*t = Time(now)
	return
}
func (t Time) MarshalJSON() ([]byte,error)  {
	b := make([]byte,0,len(timeFormat)+2)
	b = append(b,'"')
	b = time2.Time(t).AppendFormat(b,timeFormat)
	b = append(b,'"')
	return b,nil
}
func (t Time)String() string  {
	return time2.Time(t).Format(timeFormat)
}



func ParseTime(t string) (rv time2.Duration) {

	t0 := 0
	for k, _ := range t {
		v := int(t[k])
		switch {
		case v >= '0' && v <= '9':
			t0 = t0*10 + (v - '0')
		case v == 's':
			rv += time2.Duration(t0) * time2.Second
			t0 = 0
		case v == 'm':
			if k+1 < len(t) && t[k+1] == 's' {
				rv += time2.Duration(t0) * time2.Millisecond
				t0 = 0
				k++
				continue
			}
			rv += time2.Duration(t0*60) * time2.Second
			t0 = 0
		case v == 'h':
			rv += time2.Duration(t0*60*60) * time2.Second
			t0 = 0
		case v == 'd':
			rv += time2.Duration(t0*60*60*24) * time2.Second
			t0 = 0
		case v == 'w':
			rv += time2.Duration(t0*60*60*24*7) * time2.Second
			t0 = 0
		case v == 'M':
			rv += time2.Duration(t0*60*60*24*7*31) * time2.Second
			t0 = 0
		case v == 'y':
			rv += time2.Duration(t0*60*60*24*7*31*365) * time2.Second
			t0 = 0
		}
	}

	return
}

// StringToUnixTs 日期格式转换为时间戳
func StringToUnixTs(t string) int64 {
	if len(t) == 0 {
		return 0
	}
	timeLayout := "yyyy-MM-dd"
	if strings.Contains(t, ":") {
		timeLayout += " HH:mm:ss"
	}
	theTime := ToTime(timeLayout, t)
	return theTime.Unix()
}

// ToTime 时间字符串转Time
func ToTime(layout, value string) *time2.Time {
	dateTime, err := time2.Parse(layout, value)
	if err != nil {
		panic(err)
	}
	return &dateTime
}

// FormatDateTime 时间戳日期格式化
func FormatDateTime(timestamp int64, dateFormat string) string {
	return time2.Unix(timestamp, 0).Format(dateFormat)
}

// GetThisMonthFirstZeros 获取本月初时间戳
func GetThisMonthFirstZeros() int64 {
	year, month, _ := time2.Now().Date()
	return time2.Date(year, month, 1, 0, 0, 0, 0, time2.Local).Unix()
}

// GetMonthZeroTs 获取每月时间
func GetMonthZeroTs() int64 {
	t := time2.Now()
	return time2.Date(t.Year(), t.Month(), t.Day(), 0, 0, 0, 0, time2.Local).AddDate(0, 0, 1).Unix()
}

// GetTomorrowZeroTs 获取明天0点时间
func GetTomorrowZeroTs() int64 {
	t := time2.Now()
	return time2.Date(t.Year(), t.Month(), t.Day(), 0, 0, 0, 0, time2.Local).AddDate(0, 0, 1).Unix()
}

// GetTodayZeroTs 获取今天0点时间
func GetTodayZeroTs() int64 {
	t := time2.Now()
	return time2.Date(t.Year(), t.Month(), t.Day(), 0, 0, 0, 0, time2.Local).Unix()
}

// ReverseStringSlice 数组反转
func ReverseStringSlice(strs []string) []string {
	for i, j := 0, len(strs)-1; i < j; i, j = i+1, j-1 {
		strs[i], strs[j] = strs[j], strs[i]
	}
	return strs
}

// GetZeroTimeStamp 获取一段时间后的零点
func GetZeroTimeStamp(years, months, days int) int64 {
	t := time2.Now()
	return time2.Date(t.Year(), t.Month(), t.Day(), 0, 0, 0, 0, t.Location()).AddDate(years, months, days).Unix()
}

// 获取指定时间的时间戳
func GetTsByTime(time time2.Time) int32 {
	return int32(time.UTC().Unix())
}

// GetTsInt64ByTime 获取指定时间的时间戳
func GetTsInt64ByTime(time time2.Time) int64 {
	return time.UTC().Unix()
}

// 获取指定时间戳的时间
func GetTimeByTs(ts int64) time2.Time {
	time := time2.Unix(ts, 0)
	return time
}

// 获取时间间隔函数 根据秒数返回 X天X小时X分钟X秒 的结果
func GetTimeRangeInfoDay(seconds int64) string {
	var (
		day, hour, minute, second int64
	)
	if seconds >= 86400 {
		day = day / 86400
		seconds = seconds % 86400
	}
	if seconds >= 3600 {
		hour = seconds / 3600
		seconds = seconds % 3600
	}
	if seconds >= 60 {
		minute = seconds / 60
		seconds = seconds % 60
	}
	second = seconds
	return fmt.Sprintf("%d小时%d分钟%d秒", hour, minute, second)
}

// GetRemainingTimeBySeconds X天X小时X分钟X秒
func GetRemainingTimeBySeconds(seconds int64) string {
	var (
		day, hour, minute, second int64
	)
	if seconds >= 86400 {
		day = seconds / 86400
		seconds = seconds % 86400
	}
	if seconds >= 3600 {
		hour = seconds / 3600
		seconds = seconds % 3600
	}
	if seconds >= 60 {
		minute = seconds / 60
		seconds = seconds % 60
	}
	second = seconds
	return fmt.Sprintf("%d天%d小时%d分钟%d秒", day, hour, minute, second)
}
